//
//  MessageForwardingViewController.m
//
//  Created by 周成龙
//

#import "MessageForwardingViewController.h"

#import <objc/runtime.h>

// --------------------------------
@interface MessageForwardingAutoDictionary : NSObject

@property (nonatomic, copy) NSString *string;
@property (nonatomic, strong) NSDate *date;
@property (nonatomic, strong) NSNumber *number;
@property (nonatomic, strong) id opaqueObject;

@property (nonatomic, strong) NSMutableDictionary *backingStore;
@end

@implementation MessageForwardingAutoDictionary

@dynamic string, date, number, opaqueObject;

- (instancetype)init {
    if (self = [super init]) {
        _backingStore = [NSMutableDictionary new];
    }
    return self;
}

+ (BOOL)resolveInstanceMethod:(SEL)sel {
    
    NSString *seletorString = NSStringFromSelector(sel);
    
    if ([seletorString hasPrefix:@"set"]) {
        class_addMethod(self, sel, (IMP)autoDictionarySetter, "v@:@");
    }else {
        class_addMethod(self, sel, (IMP)autoDictionaryGetter, "@@:");
    }
    return YES;
}

id autoDictionaryGetter(id self, SEL _cmd) {
    
    MessageForwardingAutoDictionary *typeSelf = (MessageForwardingAutoDictionary *)self;
    NSMutableDictionary *dict = typeSelf.backingStore;
    NSString *key = NSStringFromSelector(_cmd);
    return [dict objectForKey:key];
}

void autoDictionarySetter(id self, SEL _cmd, id value) {
    
    MessageForwardingAutoDictionary *typeSelf = (MessageForwardingAutoDictionary *)self;
    NSMutableDictionary *dict = typeSelf.backingStore;
    
    // key
    NSString *seletorString = NSStringFromSelector(_cmd);
    NSMutableString *key = [seletorString mutableCopy];
    
    // :
    [key deleteCharactersInRange:NSMakeRange(key.length-1, 1)];
    // set
    [key deleteCharactersInRange:NSMakeRange(0, 3)];
    // 小写
    NSString *lowercaseString = [[key substringToIndex:1] lowercaseString];
    [key replaceCharactersInRange:NSMakeRange(0, 1) withString:lowercaseString];
    
    if (value) {
        [dict setObject:value forKey:key];
    }else {
        [dict removeObjectForKey:key];
    }
}

/**
 const char *types:
 c
 A char
 i
 An int
 s
 A short
 l
 A long
 l is treated as a 32-bit quantity on 64-bit programs.
 q
 A long long
 C
 An unsigned char
 I
 An unsigned int
 S
 An unsigned short
 L
 An unsigned long
 Q
 An unsigned long long
 f
 A float
 d
 A double
 B
 A C++ bool or a C99 _Bool
 v
 A void
 *
 A character string (char *)
 @
 An object (whether statically typed or typed id)
 #
 A class object (Class)
 :
 A method selector (SEL)
 [array type]
 An array
 {name=type...}
 A structure
 (name=type...)
 A union
 bnum
 A bit field of num bits
 ^type
 A pointer to type
 ?
 An unknown type (among other things, this code is used for function pointers)
 */
@end



// --------------------------------
@interface MessageForwardingViewController ()

@end

@implementation MessageForwardingViewController
#pragma mark - LifeCycle
+ (BOOL)resolveInstanceMethod:(SEL)sel {
    return YES;
}

- (id)forwardingTargetForSelector:(SEL)aSelector {
    return nil;
}

- (void)forwardInvocation:(NSInvocation *)anInvocation {
    
}

- (void)viewDidLoad {
    [super viewDidLoad];
    
    // 消息转发流程：
    // resolveInstanceMethod: -NO-> forwardingTargetForSelector: -NO-> forwardInvocation: -NO-> 消息未能处理
    
    
    
    /**
     实例：
     编写一个类似于字典的对象，它里面可以容纳其他对象，只不过对象直接通过属性存取其中的数据
     设计思路：由开发者添加属性，定义，并将其声明为@dynamic，而类则会自动处理相关属性值的存放与获取操作。
     */
    MessageForwardingAutoDictionary *dict = [MessageForwardingAutoDictionary new];
    dict.date = [NSDate dateWithTimeIntervalSince1970:150000000];
    NSLog(@"dict.date=%@", dict.date);
}

- (NSArray *)caculteFab:(NSInteger)count {
    NSMutableArray *tepmArr = [@[] mutableCopy ];
    NSAssert(count >= 0, @"索引小于0");
    for (int i =0; i < count; i ++) {
        [tepmArr addObject:@(accorindInexNum(i))];
    }
    return [tepmArr copy];
}

int accorindInexNum (int index) {
    if (index < 2) {
        return index == 1 ? 1 : 0;
    } else {
        return accorindInexNum(index-1) + accorindInexNum(index -2);
    }
}

@end
